/******************************************************************************
*
* Copyright (C), 2013, mophie. Co., Ltd. All Rights Reserved. 
*
* Version: v1.0.0
* $$Datae: 2013-7-5  
*
* Description:    
*   IIC Function
*
* Function List: 
* 
* History:        
*         1. $$data:  2013-7-5
*            Author:  JPM team         
*
******************************************************************************/

/********include files********************************************************/
#include "pio.h"
#include "io_api.h"

/********function list********************************************************/
/*****************************************************************************
** Function name:
**      PIO_out_config_api

** Descriptions:
**      config a gpio as out put
**
** parameters:
**      en_pull_up:     1----enable pull up 0----disable pull up
**      en_multi_drive: 1----enable multi drive 0----disable multi drive
**      pin_index:      pin number
** Returned value:
**      none
** 
*****************************************************************************/
void PIO_out_config_api(Pio *p_pio,uint8_t en_pull_up,uint8_t en_multi_drive,\
                        uint32_t pin_index)
{
      pin_index = pin_index%32;
      //disable interrupt
      p_pio->PIO_IDR = 1U<<pin_index;
      
      //pull up config
      if(en_pull_up == ENABLE)
      {
            p_pio->PIO_PUER = 1U<<pin_index;
      }
      else
      {
            p_pio->PIO_PUDR = 1U<<pin_index;
      }
      
      //multi drive config
      if(en_multi_drive == ENABLE)
      {
            p_pio->PIO_MDER = 1U<<pin_index;
      }
      else
      {
            p_pio->PIO_MDDR = 1U<<pin_index;
      }
      
      //out put enable
      p_pio->PIO_OER = 1U<<pin_index;
      //pio control enable
      p_pio->PIO_PER = 1U<<pin_index;
}

/*****************************************************************************
** Function name:
**      PIO_set_bit

** Descriptions:
**      set the io pin to high leval
**
** parameters:
**      p_pio------pointer to the i/o port
**      pin_index: pin number 0----31
**
** Returned value:
**      none
** 
*****************************************************************************/
void PIO_set_bit(Pio *p_pio,uint32_t pin_index)
{
    pin_index = pin_index%32;  
    p_pio->PIO_SODR = 1U<<pin_index;
}

/*****************************************************************************
** Function name:
**      PIO_reset_bit

** Descriptions:
**      set the io pin to low leval
**
** parameters:
**      p_pio------pointer to the i/o port
**      pin_index: pin number 0----31
**
** Returned value:
**      none
** 
*****************************************************************************/
void PIO_reset_bit(Pio *p_pio,uint32_t pin_index)
{
    pin_index = pin_index%32;  
    p_pio->PIO_CODR = 1U<<pin_index;
}

/*****************************************************************************
** Function name:
**      PIO_reset_bit

** Descriptions:
**      config a gpio as in put
**
** parameters:
**      p_pio------pointer to the i/o port
**      en_pull_up:     1----enable pull up 0----disable pull up
**      en_filter:      1----enable filter 0----disable filter
**      pin_index: pin number 0----31
**
** Returned value:
**      none
** 
*****************************************************************************/
void PIO_input_config_api(Pio *p_pio,uint8_t en_pull_up,uint8_t en_filter,\
                          uint32_t pin_index)
{
    pin_index = pin_index%32;  
    //enable pio clock
    if(p_pio == PIOA)
    {
            PMC->PMC_PCER0 |= 1U<<11;
    }
    else if(p_pio == PIOB)
    {
            PMC->PMC_PCER0 |= 1U<<12;
    }
    
    //disable interrupt
    p_pio->PIO_IDR |= 1U<< pin_index;
    
    //config pull up
    if(en_pull_up == ENABLE)
    {
         p_pio->PIO_PUER |= 1U<<pin_index;   
    }
    else
    {
         p_pio->PIO_PUDR |= 1U<<pin_index;   
    }
    
    //config filter
    if(en_filter == ENABLE)
    {
         p_pio->PIO_IFER |= 1U<<pin_index;
         p_pio->PIO_DIFSR |= 1U<<pin_index;
         p_pio->PIO_SCDR &= 0xffffc000;//(~0x00003fff);
    }
    else
    {
         p_pio->PIO_IFDR |= 1U<<pin_index;
    }
    
    //disable out put
    p_pio->PIO_ODR |= 1U<<pin_index;
   
   // 
    p_pio->PIO_PER |= 1U<<pin_index;       
}

/*****************************************************************************
** Function name:
**      PIO_read_bit

** Descriptions:
**      read the input pin state
**
** parameters:
**      p_pio------pointer to the i/o port
**      pin_index: pin number 0----31
**
** Returned value:
**      the pin state 0----low leval 1----high leval
** 
*****************************************************************************/
uint8_t PIO_read_bit(Pio *p_pio,uint32_t pin_index)
{
    pin_index = pin_index%32;  
    if((p_pio->PIO_PDSR&(1U<<pin_index)) == 0)
    {
            return(0);
    }
    return(1);
}

/*****************************************************************************
** Function name:
**      PIO_read_output_data    
** 
** Descriptions:
**      read pio output data state
**
** parameters:
**      p_pio------pointer to the i/o port
**      pin_index: pin number 0----31
**
** Returned value:
**      the output pin state 0----low leval 1----high leval
** 
*****************************************************************************/
uint8_t PIO_read_output_data(Pio *p_pio,uint32_t pin_index)
{
    pin_index = pin_index%32;  
    if((p_pio->PIO_ODSR&(1U<<pin_index)) == 0)
    {
            return(0);
    }
    return(1);
}
     
